package com.pan.admin.quartz.task;

import com.gitee.apanlh.spring.BeanContextUtils;
import com.gitee.apanlh.util.base.CollUtils;
import com.gitee.apanlh.util.base.Eq;
import com.gitee.apanlh.util.base.IteratorUtils;
import com.gitee.apanlh.util.base.MapUtils;
import com.gitee.apanlh.util.cache.local.Cache;
import com.gitee.apanlh.util.cache.local.CacheUtils;
import com.gitee.apanlh.util.log.Log;
import com.gitee.apanlh.util.thread.pool.ThreadPoolExecutorUtils;
import com.gitee.apanlh.util.valid.ValidParam;
import com.pan.admin.module.crm.entity.CrmDistributeLoanUser;
import com.pan.admin.quartz.entity.DistributeUser;
import com.pan.admin.quartz.entity.DistributeUserLogic;
import com.pan.admin.quartz.entity.LoanJfExecuteRecord;
import com.pan.admin.quartz.entity.vo.LoanProductVO;
import com.pan.admin.quartz.service.OrgDistributeService;
import com.pan.admin.quartz.service.impl.SmsServiceImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.List;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.stream.Collectors;

/**
 *  机构分发数据
 *
 *  @author Pan
 */
@Component("orgDistribute")
public class OrgDistribute {

    static final ThreadPoolExecutor POOL = ThreadPoolExecutorUtils.instanceBlocking(4, 8);
    static final Cache<Integer, Boolean> CHECK_MAP = CacheUtils.cache(MapUtils.newHashMap());

    @Autowired
    private OrgDistributeService orgDistributeService;
    @Autowired
    private SmsServiceImpl smsService;

    public void orgDistributeTask() {
        //  忽略此环境
        String activeProfile = BeanContextUtils.getApplicationContext().getEnvironment().getActiveProfiles()[0];
        if (Eq.str("prod-local", activeProfile)) {
           return ;
        }

        //  获取本地机构及启用中的全部机构ID
        List<LoanProductVO> productIdList = orgDistributeService.listProductId();
        if (ValidParam.isEmpty(productIdList)) {
            Log.get().info("无机构需要分发");
            return;
        }

        for (LoanProductVO product : productIdList) {
            Integer productId = product.getId();
            //  存在任务处理
            if (ValidParam.isNotNull(CHECK_MAP.get(productId))) {
                Log.get().info("机构id:{}, 任务执行未完成", productId);
                continue;
            }

            POOL.execute(() -> {
                CHECK_MAP.put(productId, Boolean.TRUE);

                try {
                    String productName = product.getName();
                    //  根据机构ID-获取分发的用户
                    List<Integer> loanUserIdList = orgDistributeService.listDistributeLoanUserId(productId);
                    if (ValidParam.isEmpty(loanUserIdList)) {
                        Log.get().info("机构id:{}, 无可分发的[客户]数据", productId);
                        return ;
                    }

                    //  根据机构ID-获取分发的客服
                    List<DistributeUser> userIdList = orgDistributeService.listUserId(productId);
                    if (ValidParam.isEmpty(userIdList)) {
                        Log.get().info("机构id:{}, 暂未找到分发[客服]数据", productId);
                        return ;
                    }

                    //  获取分配记录表
                    LoanJfExecuteRecord loanJfExecuteRecord = orgDistributeService.getDistributeRecord(productId, CollUtils.findFirstNotNull(userIdList, user -> user.getUserId()));
                    //  获取下一个分发的客服对象
                    DistributeUser nextDistributeUser = orgDistributeService.getLastCustomerService(userIdList, loanJfExecuteRecord);
                    if (nextDistributeUser == null) {
                        Log.get().info("机构id:{}, 无可下一个分发的客服用户,请查看是否全部禁用", productId);
                        return ;
                    }

                    // 顺序分配的客户数据
                    DistributeUserLogic distributeUserLogic = orgDistributeService.getDistributeSequential(loanUserIdList, userIdList, nextDistributeUser, productId);
                    if (ValidParam.isNull(distributeUserLogic)) {
                        Log.get().info("机构id:{}, 无分配记录数据", productId);
                        return ;
                    }

                    // 批量插入
                    orgDistributeService.batchInsert(distributeUserLogic.getDistributeLoanUserList());
                    // 更新记录
                    orgDistributeService.updateDistributeRecord(loanJfExecuteRecord, distributeUserLogic.getLastUserId(), distributeUserLogic.getLastLoanUserId(), productId);

                    // 获取分配对象
                    List<CrmDistributeLoanUser> distributeLoanUserList = distributeUserLogic.getDistributeLoanUserList();
                    // 对客服id进行去重
                    List<Integer> sendSmsUserIdList = distributeLoanUserList.stream().map(item-> item.getUserId()).distinct().collect(Collectors.toList());

                    //  根据客服id获取对应的客服电话
                    List<String> sendPhoneList = CollUtils.newArrayList();
                    IteratorUtils.array(sendSmsUserIdList, item -> {
                        DistributeUser find = CollUtils.findOne(userIdList, user -> Eq.object(item, user.getUserId()));
                        if (ValidParam.isNotNull(find)) {
                            sendPhoneList.add(find.getPhonenumber());
                        }
                    });

                    // 发送短信
                    smsService.sendCrmNotice(sendPhoneList, productName);
                } catch (Exception e) {
                    Log.get().info("机构id:{}, {}", productId, e.getMessage(), e);
                } finally {
                    CHECK_MAP.remove(productId);
                }
            });
        }
    }
}
